home *** CD-ROM | disk | FTP | other *** search
/ Graphics Plus / Graphics Plus.iso / libs / sphigs / sph_dos.lha / dos / sphsrc.v08 / sph_refresh.c < prev    next >
Encoding:
C/C++ Source or Header  |  1991-11-26  |  7.8 KB  |  327 lines

  1. #include "HEADERS.h"
  2. #include "sphigslocal.h"
  3.  
  4.  
  5. static boolean double_buffer_flag = FALSE;
  6. static int cur_screen_width, cur_screen_height;
  7. static int buffer_canvas;
  8.  
  9.  
  10.  
  11. void SPH_setDoubleBufferingFlag (boolean flag)
  12. {
  13.    if (flag == double_buffer_flag)
  14.       return;
  15.       
  16.    if (flag) {
  17.       /* USER IS TURNING ON DOUBLE BUFFERING */
  18.       /* Allocate an SRGP canvas */
  19.       SRGP_inquireCanvasSize (0, &cur_screen_width, &cur_screen_height);
  20.       buffer_canvas = SRGP_createCanvas (cur_screen_width, cur_screen_height);
  21.       /* Initialize to copy of current screen */
  22.       SRGP_useCanvas (buffer_canvas);
  23.       SRGP_copyPixel (0, SRGP_inquireCanvasExtent(0), SRGP_defPoint(0,0));
  24.    }
  25.    else {
  26.       /* USER IS DISABLING DOUBLE BUFFERING */
  27.       /* Deallocate the canvas */
  28.       SRGP_deleteCanvas (buffer_canvas);
  29.    }
  30.    
  31.    double_buffer_flag = flag;
  32. }
  33.  
  34. static void PREPARE_FOR_DRAWING (void)
  35. {
  36.    SRGP_useCanvas (double_buffer_flag ? buffer_canvas : 0);
  37. }
  38.  
  39. #define BUFFER_TO_SCREEN   TERMINATE_DRAWING
  40.  
  41. static void TERMINATE_DRAWING (void)
  42. {
  43.    if (double_buffer_flag) {
  44.       SRGP_useCanvas (0);
  45.       SRGP_copyPixel (buffer_canvas, 
  46.               SRGP_inquireCanvasExtent(0), SRGP_defPoint(0,0));
  47.    }
  48. }
  49.  
  50.  
  51. /** REFRESH ONE VIEW
  52. Should be called only if a redraw (at least) is needed!
  53.  
  54. IF wireframe rendering (raw or otherwise):
  55.     full retraversal is performed
  56. ELSE:
  57.    IF view has obsolete object list:
  58.     full retraversal
  59.    ELSE IF view has obsolete PDC vertex list:
  60.     PDC vertices are recalculated from the UVN list
  61.    ELSE 
  62.     Redrawing *only* is performed
  63.     
  64. This function resets the obsolescence flags in the view table!
  65. **/
  66.  
  67. static void
  68. RefreshOneView (int vi)
  69. {
  70.    register root_header *root;
  71.    boolean do_retraverse = FALSE;
  72.  
  73.    currentViewIndex = vi;
  74.    currentViewSpec = &(SPH_viewTable[currentViewIndex]);
  75.    currentRendermode = currentViewSpec->rendermode;
  76.  
  77.    /* Ignore this view if no roots are posted to it, or it's disabled */
  78.    if ((currentViewSpec->lowestOverlapNetwork == NULL) || 
  79.        (currentViewSpec->currently_disabled))
  80.               return;
  81.    
  82.    if ((currentViewSpec->obsolete_object_list) || 
  83.        (currentRendermode==WIREFRAME_RAW))
  84.       do_retraverse = TRUE;
  85.  
  86.  
  87.    /* Clear the viewport area */
  88.    SRGP_setClipRectangle (currentViewSpec->pdc_viewport);
  89.    SRGP_setFillStyle (SOLID);
  90.    SRGP_setColor (currentViewSpec->background_color);
  91.    SRGP_fillRectangle (currentViewSpec->pdc_viewport);
  92.    
  93.    if (do_retraverse) {
  94.       if (currentRendermode > WIREFRAME_RAW)   
  95.          OBJECT__init (currentViewSpec);
  96.       for
  97.          (root = currentViewSpec->lowestOverlapNetwork;
  98.           root != NULL;
  99.           root = root->nextHigherOverlapRoot)
  100.         SPH__traverse_network_for_display (currentViewSpec, root);
  101.    }
  102.  
  103.  
  104.    /* IF rendermode IS NOT RAW, WE NEED TO PROCESS THE OBJECTS. */
  105.    if (currentRendermode > WIREFRAME_RAW) {
  106.       if (do_retraverse) 
  107.          OBJECT__process (currentViewSpec);
  108.       else if (currentViewSpec->obsolete_pdc_vertices)
  109.          SPH__generate_pdc_vertices (currentViewSpec);
  110.       OBJECT__drawAll (currentViewSpec);
  111.    }
  112.  
  113.    /* TELL SRGP TO REFRESH SCREEN  (no-op unless X11) */
  114.    SRGP_refresh();
  115.    
  116.    /* RESET THE FLAGS */
  117.    currentViewSpec->obsolete_object_list = 
  118.       currentViewSpec->obsolete_pdc_vertices = FALSE;
  119. }
  120.  
  121.  
  122. static void
  123. WHITEWASH_RECT (srgp__rectangle r)
  124. {
  125.    SRGP_setClipRectangle (r);
  126.    SRGP_setFillStyle (SOLID);
  127.    SRGP_setColor (SRGP_WHITE);
  128.    SRGP_fillRectangle (r);
  129. }
  130.  
  131.  
  132.  
  133.  
  134. /** PERFORM REFRESH
  135. Only refreshes views that actually need to be redrawn or retraversed due to
  136. changes in objects or in the view specification
  137. **/
  138. static void
  139. PERFORM_REFRESH (void)
  140. {
  141.    register vi;
  142.    register view_spec *v;
  143.  
  144.    for (vi=0; vi <= MAX_VIEW_INDEX; vi++) {
  145.       v = &(SPH_viewTable[vi]);
  146.       if ((v->obsolete_object_list) || (v->obsolete_pdc_vertices))
  147.          RefreshOneView (vi);
  148.    }
  149. }
  150.  
  151.  
  152.  
  153. /*!*/
  154. void
  155. SPH_setImplicitRegenerationMode (int mode)
  156. {
  157.    if (mode == SPH_implicit_regeneration_mode)
  158.       return;
  159.       
  160.    if (mode==ALLOWED)
  161.      PERFORM_REFRESH();
  162.      
  163.    SPH_implicit_regeneration_mode = mode;
  164. }
  165.  
  166.  
  167. /** REGENERATE SCREEN
  168. Called by the application, typically when it has turned off 
  169.    implicit regeneration.
  170. Thus, we can't assume we're just repairing screen damage!
  171. But it does not retraverse or recompute PDCs
  172.    unless a true data change occurred, so it is efficient.
  173. **/
  174. void
  175. SPH_regenerateScreen (void)
  176. {
  177.    register vi;
  178.  
  179.    PREPARE_FOR_DRAWING();
  180.    for (vi=0; vi <= MAX_VIEW_INDEX; vi++)
  181.        RefreshOneView (vi);
  182.    TERMINATE_DRAWING();
  183.  
  184. }
  185.  
  186.  
  187. /** REPAINT SCREEN
  188. Called  when we are told by the window manager that an
  189.    update should occur to handle damage.
  190. ASSUMES no data change has taken place since screen last painted.
  191. Very efficient if double buffering happens to be on.
  192. CURRENTLY NOT INSTALLED.  Moreover, it's not needed when backing store is on.
  193. **/
  194. void
  195. SPH__repaintScreen (void)
  196. {
  197.    if (double_buffer_flag)
  198.       BUFFER_TO_SCREEN();
  199.    else
  200.       SPH_regenerateScreen();
  201. }
  202.  
  203.  
  204.  
  205. /*!*/
  206. void
  207. SPH_setRenderingMode (int viewindex, int value)
  208. {
  209.    SPH_viewTable[viewindex].rendermode = value;
  210.    
  211.    SPH_viewTable[viewindex].obsolete_object_list = TRUE;
  212.    if (SPH_implicit_regeneration_mode == ALLOWED) {
  213.       PREPARE_FOR_DRAWING();
  214.       RefreshOneView (viewindex);
  215.       TERMINATE_DRAWING();
  216.    }
  217. }
  218.  
  219.  
  220.  
  221.  
  222. /*!*/
  223. void
  224. SPH__refresh_structure_close (int structID)
  225. {
  226.    register int v;
  227.  
  228.    PREPARE_FOR_DRAWING();
  229.    for (v=0; v<=MAX_VIEW_INDEX; v++)
  230.      if (TestBit(SPH_viewTable[v].descendent_list, structID)) {
  231.         SPH_viewTable[v].obsolete_object_list = TRUE;
  232.         if (SPH_implicit_regeneration_mode == ALLOWED)
  233.            RefreshOneView (v);
  234.      }
  235.    TERMINATE_DRAWING();
  236. }
  237.       
  238.  
  239.  
  240.  
  241. /*!*/
  242. void SPH__refresh_post (int view)
  243. {
  244.    PREPARE_FOR_DRAWING();
  245.    SPH_viewTable[view].obsolete_object_list = TRUE;
  246.    if (SPH_implicit_regeneration_mode == ALLOWED)
  247.       RefreshOneView (view);
  248.    TERMINATE_DRAWING();
  249. }
  250.  
  251.  
  252.  
  253.  
  254. /** Refreshing after an unpost
  255. If the view no longer has any posted members, do a whitewash!
  256. **/
  257. void SPH__refresh_unpost (int view)
  258. {
  259.    PREPARE_FOR_DRAWING();
  260.    if (SPH_viewTable[view].highestOverlapNetwork == NULL)
  261.       WHITEWASH_RECT (SPH_viewTable[view].pdc_viewport);
  262.    else {
  263.       SPH_viewTable[view].obsolete_object_list = TRUE;
  264.       if (SPH_implicit_regeneration_mode == ALLOWED)
  265.          RefreshOneView (view);
  266.    }
  267.    TERMINATE_DRAWING();
  268. }
  269.  
  270.  
  271.  
  272. /** Refreshing after a viewport change
  273. Should we whitewash the area that is occupied by the current
  274. viewport for this view?
  275.  Only if:
  276.           1) There is at least one structure posted to the view.
  277.    AND  2) The intersection of the current vp and the new vp is NOT
  278.            equal to the current vp.
  279.            
  280.  LATER: we will have to repair damage done to overlapping
  281.              innocent-bystander views.
  282. **/
  283. void SPH__refresh_viewport_change (int viewIndex, srgp__rectangle old_viewport_rect)
  284. {
  285.    srgp__rectangle intersection;
  286.    
  287.    PREPARE_FOR_DRAWING();
  288.    if (GEOM_computeRectIntersection(old_viewport_rect, 
  289.                            SPH_viewTable[viewIndex].pdc_viewport,
  290.                         &intersection))
  291.        /* GEOM SAYS THEY DO INTERSECT */
  292.        if ( ! memcmp(&intersection,&old_viewport_rect, sizeof(srgp__rectangle))) 
  293.           /* AH!  The intersection is equal to the original viewport. */
  294.           /* Don't whitewash! */
  295.           goto dorefresh_vpc;
  296.    
  297.    /* Perform the whitewash! */
  298.    WHITEWASH_RECT (old_viewport_rect);
  299.        
  300.  dorefresh_vpc:
  301.    SPH_viewTable[viewIndex].obsolete_object_list = TRUE;
  302.    if (SPH_implicit_regeneration_mode == ALLOWED)
  303.       RefreshOneView (viewIndex);
  304.       
  305.    TERMINATE_DRAWING();
  306. }
  307.  
  308.  
  309. void SPH_disableView (int v)
  310. {
  311.   if (SPH_viewTable[v].currently_disabled)
  312.      return;
  313.      
  314.   WHITEWASH_RECT (SPH_viewTable[v].pdc_viewport);
  315.   SPH_viewTable[v].currently_disabled = TRUE;
  316. }
  317.  
  318. void SPH_enableView (int v)
  319. {
  320.   if ( ! SPH_viewTable[v].currently_disabled)
  321.      return;
  322.      
  323.   SPH_viewTable[v].currently_disabled = FALSE;
  324.   SPH__refresh_viewport_change (v, SPH_viewTable[v].pdc_viewport);
  325. }
  326.  
  327.